from fastapi import Request, HTTPException
from starlette.middleware.base import BaseHTTPMiddleware
from app.core.jwt_utils import verify_token
from app.config.settings import settings  # 假设存在配置文件定义白名单
from app.core.local_logging import setup_logging

logger = setup_logging()

class TokenVerificationMiddleware(BaseHTTPMiddleware):
    async def dispatch(self, request: Request, call_next):
        # 跳过OPTIONS预检请求（关键修改）
        if request.method == "OPTIONS":
            logger.debug(f"跳过预检请求: {request.method} {request.url.path}")
            return await call_next(request)

        # 跳过白名单路径（如登录、注册等公开接口）
        if request.url.path in settings.AUTH_WHITELIST:
            logger.debug(f"跳过白名单路径检查: {request.url.path}")
            return await call_next(request)

        # 从请求头获取Authorization字段
        logger.debug(f"检查Authorization头: {request.headers}")
        auth_header = request.headers.get("Authorization") or request.headers.get("authorization")
        if not auth_header or not auth_header.startswith("Bearer "):
            logger.warning(f"无效的Authorization头: {auth_header}")
            raise HTTPException(status_code=200, detail="未登录")

        # 提取并验证token
        token = auth_header.split(" ")[1]
        payload = verify_token(token)
        if not payload or "sub" not in payload:
            logger.warning(f"无效的token: {token}")
            raise HTTPException(status_code=200, detail="Token无效或已过期")

        # 将用户名添加到请求对象中（供后续路由使用）
        request.state.username = payload["sub"]
        return await call_next(request)